import React from "react";
import { cn } from "~/components/lib/utils";
import { api } from "~/utils/api";
import { type HostStatistics } from "~/server/api/routers/host";

// Define the severity counts interface for internal use
export interface VulnerabilitySeverityCounts {
  critical: number;
  high: number;
  medium: number;
  low: number;
  informational: number;
}

interface VulnerabilityBarGraphProps {
  hostId: string; // Required prop to fetch data by host ID
  height?: number;
  className?: string;
}

export function VulnerabilityBarGraph({
  hostId,
  height = 8,
  className,
}: VulnerabilityBarGraphProps) {
  // Fetch the statistics directly using the hostId
  const hostStatsQuery = api.host.getHostStatistics.useQuery({ hid: hostId });

  // Show loading indicator while fetching data
  if (hostStatsQuery.isLoading) {
    return (
      <div
        className={cn(
          "flex w-full items-center justify-center py-2",
          className
        )}
      >
        <div className="h-4 w-4 animate-spin rounded-full border-b-2 border-t-2 border-violet-500"></div>
      </div>
    );
  }

  // Get severity counts from API data
  const severityCounts: VulnerabilitySeverityCounts = hostStatsQuery.data
    ?.hostSeverityCounts || {
    critical: 0,
    high: 0,
    medium: 0,
    low: 0,
    informational: 0,
  };

  // Calculate the total count of vulnerabilities
  const total =
    severityCounts.critical +
    severityCounts.high +
    severityCounts.medium +
    severityCounts.low +
    severityCounts.informational;

  // If there are no vulnerabilities, display a placeholder
  if (total === 0) {
    return (
      <div className={cn("text-xs text-gray-400", className)}>
        No vulnerabilities
      </div>
    );
  }

  // Calculate percentages for each severity
  const criticalPercentage = (severityCounts.critical / total) * 100;
  const highPercentage = (severityCounts.high / total) * 100;
  const mediumPercentage = (severityCounts.medium / total) * 100;
  const lowPercentage = (severityCounts.low / total) * 100;
  const infoPercentage = (severityCounts.informational / total) * 100;

  return (
    <div className={cn("w-full", className)}>
      {/* Summary of vulnerabilities as text */}
      <div className="mb-1 flex justify-between text-xs">
        <span>Vulnerabilities</span>
        <span className="font-medium">{total}</span>
      </div>

      {/* The actual bar graph */}
      <div
        className="flex w-full overflow-hidden rounded-full"
        style={{ height: `${height}px` }}
      >
        {/* Critical vulnerabilities - red */}
        {severityCounts.critical > 0 && (
          <div
            className="bg-red-500"
            style={{ width: `${criticalPercentage}%` }}
            title={`${severityCounts.critical} Critical`}
          />
        )}

        {/* High vulnerabilities - orange */}
        {severityCounts.high > 0 && (
          <div
            className="bg-orange-500"
            style={{ width: `${highPercentage}%` }}
            title={`${severityCounts.high} High`}
          />
        )}

        {/* Medium vulnerabilities - yellow */}
        {severityCounts.medium > 0 && (
          <div
            className="bg-yellow-500"
            style={{ width: `${mediumPercentage}%` }}
            title={`${severityCounts.medium} Medium`}
          />
        )}

        {/* Low vulnerabilities - green */}
        {severityCounts.low > 0 && (
          <div
            className="bg-green-500"
            style={{ width: `${lowPercentage}%` }}
            title={`${severityCounts.low} Low`}
          />
        )}

        {/* Informational vulnerabilities - blue */}
        {severityCounts.informational > 0 && (
          <div
            className="bg-blue-500"
            style={{ width: `${infoPercentage}%` }}
            title={`${severityCounts.informational} Informational`}
          />
        )}
      </div>

      {/* Legend showing total counts by severity */}
      <div className="mt-1 flex flex-wrap gap-2 text-xs">
        {severityCounts.critical > 0 && (
          <span className="flex items-center">
            <span className="mr-1 h-2 w-2 rounded-full bg-red-500"></span>
            {severityCounts.critical} Critical
          </span>
        )}
        {severityCounts.high > 0 && (
          <span className="flex items-center">
            <span className="mr-1 h-2 w-2 rounded-full bg-orange-500"></span>
            {severityCounts.high} High
          </span>
        )}
        {severityCounts.medium > 0 && (
          <span className="flex items-center">
            <span className="mr-1 h-2 w-2 rounded-full bg-yellow-500"></span>
            {severityCounts.medium} Medium
          </span>
        )}
        {severityCounts.low > 0 && (
          <span className="flex items-center">
            <span className="mr-1 h-2 w-2 rounded-full bg-green-500"></span>
            {severityCounts.low} Low
          </span>
        )}
        {severityCounts.informational > 0 && (
          <span className="flex items-center">
            <span className="mr-1 h-2 w-2 rounded-full bg-blue-500"></span>
            {severityCounts.informational} Info
          </span>
        )}
      </div>
    </div>
  );
}

// A more compact version for use in table cells
export function VulnerabilityBarGraphCompact({
  hostId,
  height = 6,
  className,
}: VulnerabilityBarGraphProps) {
  // Fetch the statistics directly using the hostId
  const hostStatsQuery = api.host.getHostStatistics.useQuery({ hid: hostId });

  // Show loading indicator while fetching data
  if (hostStatsQuery.isLoading) {
    return (
      <div
        className={cn(
          "flex h-6 items-center justify-start text-xs text-gray-400",
          className
        )}
      >
        <div className="mr-2 h-3 w-3 animate-spin rounded-full border-b-2 border-t-2 border-violet-500"></div>
        Loading...
      </div>
    );
  }

  // Get severity counts from API data
  const severityCounts: VulnerabilitySeverityCounts = hostStatsQuery.data
    ?.hostSeverityCounts || {
    critical: 0,
    high: 0,
    medium: 0,
    low: 0,
    informational: 0,
  };

  const total =
    severityCounts.critical +
    severityCounts.high +
    severityCounts.medium +
    severityCounts.low +
    severityCounts.informational;

  if (total === 0) {
    return (
      <div className={cn("text-xs text-gray-400", className)}>
        No vulnerabilities
      </div>
    );
  }

  const criticalPercentage = (severityCounts.critical / total) * 100;
  const highPercentage = (severityCounts.high / total) * 100;
  const mediumPercentage = (severityCounts.medium / total) * 100;
  const lowPercentage = (severityCounts.low / total) * 100;
  const infoPercentage = (severityCounts.informational / total) * 100;

  return (
    <div className={cn("flex w-full flex-col", className)}>
      <div className="flex justify-between text-xs">
        <span>{total} vulnerabilities</span>
        {severityCounts.critical > 0 && (
          <span className="text-red-500">
            {severityCounts.critical} critical
          </span>
        )}
      </div>

      <div
        className="mt-1 flex w-full overflow-hidden rounded-full"
        style={{ height: `${height}px` }}
      >
        {severityCounts.critical > 0 && (
          <div
            className="bg-red-500"
            style={{ width: `${criticalPercentage}%` }}
            title={`${severityCounts.critical} Critical`}
          />
        )}
        {severityCounts.high > 0 && (
          <div
            className="bg-orange-500"
            style={{ width: `${highPercentage}%` }}
            title={`${severityCounts.high} High`}
          />
        )}
        {severityCounts.medium > 0 && (
          <div
            className="bg-yellow-500"
            style={{ width: `${mediumPercentage}%` }}
            title={`${severityCounts.medium} Medium`}
          />
        )}
        {severityCounts.low > 0 && (
          <div
            className="bg-green-500"
            style={{ width: `${lowPercentage}%` }}
            title={`${severityCounts.low} Low`}
          />
        )}
        {severityCounts.informational > 0 && (
          <div
            className="bg-blue-500"
            style={{ width: `${infoPercentage}%` }}
            title={`${severityCounts.informational} Informational`}
          />
        )}
      </div>
    </div>
  );
}
